package com.gosling.cloudspace.aop;

import cn.hutool.core.collection.CollectionUtil;
import com.alibaba.excel.annotation.ExcelProperty;
import io.swagger.annotations.ApiModelProperty;
import org.apache.commons.lang3.StringUtils;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;

import java.lang.reflect.Field;
import java.util.Arrays;
import java.util.List;
import java.util.regex.Matcher;
import java.util.regex.Pattern;

/**
 * 驼峰 下划线 互换
 *
 * @author lihonglin
 * @date 2022/5/27 10:56
 */
public class CaseTool {

    public static final Logger logger = LoggerFactory.getLogger(CaseTool.class);
    public static final List<String> IGNORE_LIST = Arrays.asList("serialVersionUID", "id");
    public static final String SQL_LAST = "\" 的值太大";

    public static String humpToUnderline(String str) {
        String regex = "([A-Z])";
        Matcher matcher = Pattern.compile(regex).matcher(str);
        while (matcher.find()) {
            String target = matcher.group();
            str = str.replaceAll(target, "_" + target.toLowerCase());
        }
        return str.toUpperCase();
    }

    /**
     * 驼峰转下划线
     * Caused by: java.sql.SQLException: ORA-12899: 列 "MOBAOPAY_AUDIT"."MERCHANT_BATCH_ORIGIN_DATA"."LEGAL_PERSON_CERT_TYPE" 的值太大 (实际值: 2, 最大值: 1)
     *
     * @param e 目标字符串
     * @return: java.lang.String
     */
    public static String sqlFieldLong(Exception e, Object o) throws Exception {
        String message = e.getMessage();
        message = message.replaceAll("[\r\n]", "");
        if (message.contains("java.sql.SQLException") || message.contains("的值太大") || message.contains("ORA-12899")) {
            message = message.substring(0, message.indexOf("### The error"));
            Field[] fields = o.getClass().getDeclaredFields();
            for (Field field : fields) {
                field.setAccessible(true);
                String fieldName = field.getName();
                if (IGNORE_LIST.contains(fieldName)) {
                    continue;
                }
                String toUnderline = humpToUnderline(fieldName);
                if (message.contains(toUnderline)) {
                    fieldName = message.substring(message.indexOf(toUnderline), message.indexOf(SQL_LAST));
                    if (fieldName.equalsIgnoreCase(toUnderline)) {
                        message = message.length() > 200 ? message.substring(0, 200) : message;
                        StringBuilder msg = new StringBuilder("字段超长[");
                        if (field.isAnnotationPresent(ExcelProperty.class)) {
                            ExcelProperty excel = field.getAnnotation(ExcelProperty.class);
                            if (CollectionUtil.isNotEmpty(Arrays.asList(excel.value()))) {
                                msg.append(excel.value()[0]);
                            }
                        } else if (field.isAnnotationPresent(ApiModelProperty.class)) {
                            ApiModelProperty api = field.getAnnotation(ApiModelProperty.class);
                            if (StringUtils.isNotBlank(api.value())) {
                                msg.append(api.value());
                            }
                        }
                        msg.append("]message:");
                        msg.append(message);
                        logger.error(msg.toString());
                        throw new Exception(msg.toString());
                    }
                }
            }
        }
        throw e;
    }

}